-------------------------------------------------------------------------------------
-- NUeva tabla en esquema abaco_utiles para modelos de listas de precios por rubro -- 
-------------------------------------------------------------------------------------

CREATE TABLE abaco_utiles.modelos_listas
(
  rubro character varying(50) NOT NULL,
  proveedor character varying(100) NOT NULL,
  lineasaborrar integer,  
  titulo  character varying(1000) NOT NULL, 
  lineastitulo integer NOT NULL,
  col_codarti integer,
  col_rep integer,
  col_repd integer,
  col_iva integer,
  col_vta integer,
  col_vtad integer,
  col_desp1 integer,
  col_desp2 integer,
  col_desp3 integer,
  CONSTRAINT modelos_listas_pkey PRIMARY KEY (rubro)
)
WITH (
  OIDS=TRUE
);
ALTER TABLE abaco_utiles.modelos_listas
  OWNER TO abacouser;

COMMENT ON TABLE abaco_utiles.modelos_listas IS 'Modelos de Listas de Precios que llegan en excel';
COMMENT ON COLUMN abaco_utiles.modelos_listas.rubro IS 'Rubro principal de articulos sobre el que se aplica la lista';
COMMENT ON COLUMN abaco_utiles.modelos_listas.proveedor IS 'Proveedor al que pertenece. Solo informativo';
COMMENT ON COLUMN abaco_utiles.modelos_listas.lineasaborrar IS 'Cantidad de lineas al inicio a borrar. No incluye encabezados';
COMMENT ON COLUMN abaco_utiles.modelos_listas.titulo IS 'Header de encabezados de columna como los manda el proveedor';
COMMENT ON COLUMN abaco_utiles.modelos_listas.lineastitulo IS 'Cantidad de lineas de encabezados';
COMMENT ON COLUMN abaco_utiles.modelos_listas.col_codarti IS 'Numero de columna de la lista excel correspondiente al codigo de articulo';
COMMENT ON COLUMN abaco_utiles.modelos_listas.col_rep IS 'Numero de columna de la lista excel correspondiente al precio de reposicion en pesos';
COMMENT ON COLUMN abaco_utiles.modelos_listas.col_repd IS 'Numero de columna de la lista excel correspondiente al precio de reposicion en dolares';
COMMENT ON COLUMN abaco_utiles.modelos_listas.col_iva IS 'Numero de columna de la lista excel correspondiente al iva. Para usar en los distintos de 21';
COMMENT ON COLUMN abaco_utiles.modelos_listas.col_vta IS 'Numero de columna de la lista excel correspondiente al precio de venta';
COMMENT ON COLUMN abaco_utiles.modelos_listas.col_vtad IS 'Numero de columna de la lista excel correspondiente al precio de venta en dolares';
COMMENT ON COLUMN abaco_utiles.modelos_listas.col_desp1 IS 'Numero de columna de la lista excel correspondiente al descuento 1 del proveedor';
COMMENT ON COLUMN abaco_utiles.modelos_listas.col_desp2 IS 'Numero de columna de la lista excel correspondiente al descuento 2 del proveedor';
COMMENT ON COLUMN abaco_utiles.modelos_listas.col_desp3 IS 'Numero de columna de la lista excel correspondiente al descuento 3 del proveedor';
-------------------------------------------------------------------------------------------------------




----------------------------------------------------------------------------------------------------
-- Funciones usadas para generar rubros, subrubros, articulos y actualizacion de lista de precios --
-- desde archivos csv. Se generan estas fuciones en el esquema abaco_utiles                       --


--------------------------------------------------------------------------------------------
-- Funcion usada para generar rubros, subrubros y articulos, a partir de un archivo csv. ---
--------------------------------------------------------------------------------------------


-- Function: abaco_utiles.migrar_rubros_y_articulos_3n(character varying, character varying, integer)

-- DROP FUNCTION abaco_utiles.migrar_rubros_y_articulos_3n(character varying, character varying, integer);

CREATE OR REPLACE FUNCTION abaco_utiles.migrar_rubros_y_articulos_3n(character varying, character varying, integer)
  RETURNS character varying AS
$BODY$
DECLARE

vraiz     ALIAS FOR $1;
vcuit     ALIAS FOR $2;
vruta     ALIAS FOR $3; 

crubros      REFCURSOR;

vcont     integer;
vcodrub1  character varying(50);
vprefijo  character varying(4); 

vcadena   character varying;
vservidor character varying;

BEGIN

-- Esta funcion permite crear rubros, hasta con tres niveles de profundidad, a partir de un rubro padre ingresado como parametro
-- y crear los articulos correspondientes a dichos rubros, a partir de un archivo csv.

-- El primer parametro indica el rubro donde se darán de alta los articulos
-- El segundo parametro es el cuit del cliente que es obligatorio para el caso que la base no sea local 
-- El tercer parametro se utiliza para indicar la ruta desde donde se leera el archivo csv con los articulos 
--  1  para bases locales 
--  2  para bases en Hosting
--  3  para bases en Datacenter (fibercorp) 


-- El archivo debe venir sin titulos y con los campos delimitados por punto y coma.
-- La campos corresponden a  codigo de articulo; descripcion, nombre rubro1, nombre rubro2, nombre rubro3, precio 

-- Puede usarse para menos niveles de rubro, pero en esos casos las columnas correspondientes deben venir en blanco  
-- Tambien pueden venir en la lista articulos con distintos niveles de profundidad, pero siempre los niveles que falten 
-- deben venir en blanco.

-- El nombre sel archivo es 'articulos.csv' y para las bases locales dede estar en la carpeta 'c:/abaco/gestion/importar'


-- El rubro padre (parametro) debe estar creado en el sistema y debe tener un prefijo de hasta cuatro caracteres. 

-- El codigo con que el articulo se dará de alta en abaco es el prefijo seguido del codigo que viene en la lista.

-- Los rubros del primer nivel se crearan con una numeración consecutiva a partir de 1, y los nombres son los correspondientes 
-- a la columna rubro 1 de la lista.

-- Con el mismo criterio, para cada uno de los rubros de primer nivel se crearan (si hubiesen) los rubros de segundo nivel 
-- con una secuencia consecutiva a partir de 1 y los nombres se tomaran de la columna correspondiente a rubro 2 de la lista.

-- Por ultimo para cada uno de los rubros de segundo nivel se crearan (si hubiesen) los rubros de tercer nivel con una 
-- secuencia consecutiva a partir de 1 y los nombres se tomaran de la columna correspondiente al rubro 3 de la lista.
   


SET CLIENT_ENCODING TO LATIN1;

select count(*) from artr where tipoarta = 'A' and cod = vraiz into vcont;
if vcont = 0 then 
   RAISE EXCEPTION 'No existe el rubro ingresado'; 
end if;

if trim(vcuit) = '' and vruta <> 1 then
   RAISE EXCEPTION 'Debe ingresar el cuit del cliente, separado por guiones'; 
end if;

if vruta not in (1, 2, 3) then
   RAISE EXCEPTION 'El servidor debe corresponder a los codigis 1, 2 o 3';
end if;


CREATE TABLE abaco_utiles.renglones (  renglon character varying(2000) ) WITH ( OIDS=TRUE );

if vruta = 1 then
   copy abaco_utiles.renglones from 'c:/abaco/gestion/importar/articulos.csv';
  else
    if vruta = 2 then
       vservidor:= '/var/www/html/implementacion_datos/clientes/'; -- Hosting
     else
       vservidor:= '/datacenter/var/www/html/implementacion_datos/clientes/'; -- Datacenter (fibercorp)
    end if;
    vcadena:= 'copy abaco_utiles.renglones from ''' || vservidor || vcuit || '/' || 'articulos.csv' || '''';
    EXECUTE vcadena; 
end if;



CREATE TABLE abaco_utiles.arti
(
  codart	character varying(100),
  nombart       character varying(100),
  rub1		character varying(100),
  rub2		character varying(100),
  rub3		character varying(100),
  codrub1	character varying(50),
  codrub2	character varying(50),
  codrub3	character varying(50),
  idart         integer,
  codartr1      character varying(50),
  codartr2       character varying(50),
  codartr3       character varying(50),
  codartr       character varying(50),
  precio        character(16)   
)
WITH (OIDS=TRUE);


CREATE TABLE abaco_utiles.rubros
(
  nombre	character varying(100),
  codigo	character varying(50)
)
WITH (OIDS=TRUE);


CREATE TABLE abaco_utiles.subrubros
(
  nombre	character varying(100),

  padre	        character varying(50),
  
  codigo	character varying(50)
)
WITH (OIDS=TRUE);


CREATE TABLE abaco_utiles.repetidos
(
 
  codigo	character varying(50),

  ocurrencias   integer
)
WITH (OIDS=TRUE);


insert into abaco_utiles.arti (codart, nombart, rub1, rub2, rub3,  precio)
select trim(split_part(renglon, ';', 1)), 
       substring(trim(split_part(renglon, ';', 2)), 1, 100), substring(trim(split_part(renglon, ';', 3)),1, 100), 
       substring(trim(split_part(renglon, ';', 4)), 1, 100), substring(trim(split_part(renglon, ';', 5)), 1, 100),
       substring(trim(split_part(renglon, ';', 6)), 1, 16)
from abaco_utiles.renglones where trim(split_part(renglon, ';', 3)) <> '' ;

-- Se borran los articulos repetidos para que lueego no de error el insert en la tabla art.
insert into abaco_utiles.repetidos (codigo, ocurrencias)
select codart, count(*) from abaco_utiles.arti
group by codart
having count(*) > 1;

delete from abaco_utiles.arti where codart in (select codigo from abaco_utiles.repetidos);
---------------

update abaco_utiles.arti set rub1 = null  where trim(rub1) = '';
update abaco_utiles.arti set rub2 = null  where trim(rub2) = '';
update abaco_utiles.arti set rub3 = null  where trim(rub3) = '';

update abaco_utiles.arti set codrub1 = null;
update abaco_utiles.arti set codrub2 = null;
update abaco_utiles.arti set codrub3 = null;

update abaco_utiles.arti set codartr1 = null;
update abaco_utiles.arti set codartr2 = null;
update abaco_utiles.arti set codartr3 = null;

update abaco_utiles.arti set codartr = null;

DROP SEQUENCE IF EXISTS abaco_utiles.seq_rub;
CREATE SEQUENCE abaco_utiles.seq_rub
  INCREMENT 1
  MINVALUE 1
  MAXVALUE 9223372036854775807
  START 1
  CACHE 1;
ALTER TABLE abaco_utiles.seq_rub
  OWNER TO abacouser;

insert into abaco_utiles.rubros(nombre)
select distinct(rub1)from abaco_utiles.arti order by rub1;

update abaco_utiles.rubros set codigo = lpad(cast(nextval('abaco_utiles.seq_rub') as char(3)), 3, '0');

update abaco_utiles.arti arti set codrub1 = rubros.codigo  
from abaco_utiles.rubros  
where arti.rub1 = rubros.nombre;

update abaco_utiles.arti set codartr1 = vraiz || '.' || codrub1
where codrub1 is not null;


----------------------------------
--- Loop para generar los rubros de segundo nivel para cada rubro del primer nivel

OPEN crubros FOR
(
SELECT codigo 
FROM abaco_utiles.rubros 
ORDER BY codigo
);

LOOP
FETCH crubros INTO vcodrub1;
EXIT WHEN (NOT FOUND);


ALTER SEQUENCE abaco_utiles.seq_rub RESTART WITH 1;

delete from abaco_utiles.subrubros;

insert into abaco_utiles.subrubros(nombre, padre)
select distinct(rub2), vcodrub1 from abaco_utiles.arti 
where codrub1 = vcodrub1 and rub2 is not null
order by rub2;

update abaco_utiles.subrubros set codigo = lpad(cast(nextval('abaco_utiles.seq_rub') as char(3)), 3, '0');

update abaco_utiles.arti arti set codrub2 = subrubros.codigo 
from abaco_utiles.subrubros  
where codrub1 = vcodrub1 and arti.rub2 = subrubros.nombre;


END LOOP;

CLOSE crubros;

update abaco_utiles.arti set codartr2 = codartr1 || '.' || codrub2
where codrub1 is not null and codrub2 is not null;


-------------------------------------

-- Se borra la tabla auxiliar de rubros y se vuelve a llenar, pero ahora con los rubros de nivel 2
delete from abaco_utiles.rubros;

insert into abaco_utiles.rubros (codigo)
select distinct(codartr2) 
from abaco_utiles.arti 
order by codartr2;

--- Loop para generar los rubros de tercer nivel para cada rubro del segundo nivel

OPEN crubros FOR
(
SELECT codigo 
FROM abaco_utiles.rubros 
ORDER BY codigo
);

LOOP
FETCH crubros INTO vcodrub1;
EXIT WHEN (NOT FOUND);


ALTER SEQUENCE abaco_utiles.seq_rub RESTART WITH 1;

delete from abaco_utiles.subrubros;

insert into abaco_utiles.subrubros(nombre, padre)
select distinct(rub3), codartr2 from abaco_utiles.arti 
where codartr2 = vcodrub1 and rub3 is not null
order by rub3;

update abaco_utiles.subrubros set codigo = lpad(cast(nextval('abaco_utiles.seq_rub') as char(3)), 3, '0');

update abaco_utiles.arti arti set codrub3 = subrubros.codigo 
from abaco_utiles.subrubros  
where codartr2 = vcodrub1 and arti.rub3 = subrubros.nombre;


END LOOP;

CLOSE crubros;


-------------------------------------

update abaco_utiles.arti set codartr3 = codartr2 || '.' || codrub3
where codrub1 is not null and codrub2 is not null and codrub3 is not null;

update abaco_utiles.arti set codartr = coalesce(codartr3, codartr2, codartr1);

---INSERT DE RUBROS SEGUN SU NIVEL  ---

-- rubro 1
insert into artr(cod, tipoarta, nombre, aceptaitem, accesosucursales, accesousuarios, nombrerubroaart)
select distinct(codartr1), 'A', rub1, case when codartr1 = codartr then 'S' else 'N' end as aceptaitem, '*', '*', 'N' 
from abaco_utiles.arti 
where codartr1 is not null
order by codartr1;

-- rubro 2
insert into artr(cod, tipoarta, nombre, aceptaitem, accesosucursales, accesousuarios, nombrerubroaart)
select distinct(codartr2), 'A', rub2, case when codartr2 = codartr then 'S' else 'N' end as aceptaitem, '*', '*', 'N' 
from abaco_utiles.arti 
where codartr2 is not null
order by codartr2;

-- rubro 3
insert into artr(cod, tipoarta, nombre, aceptaitem, accesosucursales, accesousuarios, nombrerubroaart)
select distinct(codartr3), 'A', rub3, case when codartr3 = codartr then 'S' else 'N' end as aceptaitem, '*', '*', 'N' 
from abaco_utiles.arti 
where codartr3 is not null
order by codartr3;

---Se recupera el prefijo para hacer insert de articulos---

select preitem from artr where cod = vraiz into vprefijo;

---INSERT DE ARTICULOS---

insert into art(id, cod, nombre, tipoarta, codartr, 
                              calccant, registrastock, modifnombre, puederegalar, stkcomp, 
                              accesosucursales, cantlinea, accesousuarios) 
select getnextid('art') as id, vprefijo || codart as cod,
       paso_a_minusculas(nombart) as nombre,
       'A' as tipoarta, codartr, 
       'N' as calccant, 'S' as registrastock, 'N' as modifnombre, 'N' as puederegalar, 'N' as stkcomp, 
       '*' as accesosucursales, 'U' as cantlinea, '*' as accesousuarios
from abaco_utiles.arti
where codart is not null;

RETURN '';
END;
$BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION abaco_utiles.migrar_rubros_y_articulos_3n(character varying, character varying, integer)
  OWNER TO abacouser;


-----------------------------------------------------------------------------------------------------------

------------------------------------------------------------------------------------------------
--- Funcion para cargar articulos dentro de un rubro determinado, a partir de un archivo csv ---
------------------------------------------------------------------------------------------------

-- Function: abaco_utiles.migrar_articulos_de_un_rubro(character varying, character varying, integer)

-- DROP FUNCTION abaco_utiles.migrar_articulos_de_un_rubro(character varying, character varying, integer);

CREATE OR REPLACE FUNCTION abaco_utiles.migrar_articulos_de_un_rubro(character varying, character varying, integer)
  RETURNS character varying AS
$BODY$
DECLARE

vrubro    ALIAS FOR $1;
vcuit     ALIAS FOR $2;
vruta     ALIAS FOR $3; 

vcont     integer;
vprefijo  character varying(20); 
vraiz     character varying(50); 
vaceptaiem character varying(1); 

vcadena   character varying;
vservidor character varying;


BEGIN

--- Esta funcion incorpora articulos dentro de un rubro determinado, a partir de un archivo csv.

-- El primer parametro indica el rubro donde se darán de alta los articulos
-- El segundo parametro es el cuit del cliente que es obligatorio para el caso que la base no sea local 
-- El tercer parametro se utiliza para indicar la ruta desde donde se leera el archivo csv con los articulos 
--  1  para bases locales 
--  2  para bases en Hosting
--  3  para bases en Datacenter (fibercorp) 

-- El archivo debe venir sin titulos y con los campos delimitados por punto y coma.
-- La campos corresponden a  codigo de articulo; descripcion, precio. 

-- El nombre sel archivo es 'articulos.csv' y para las bases locales dede estar en la carpeta 'c:/abaco/gestion/importar'

--- El rubro debe estar configurado para aceptar items y puede ser de cualquier nivel, pero el rubro raiz, del que
--- el desciende debe tener un prefijo de hasta 4 caracteres, que es el que se utilizara para codificar los articulos.

-- El codigo con que el articulo se dará de alta en abaco es el prefijo seguido del codigo que viene en la lista.


SET CLIENT_ENCODING TO LATIN1;

select count(*) from artr where tipoarta = 'A' and cod = vrubro into vcont;
if vcont = 0 then 
   RAISE EXCEPTION 'No existe el rubro ingresado'; 
end if;

if trim(vcuit) = '' and vruta <> 1 then
   RAISE EXCEPTION 'Debe ingresar el cuit del cliente, separado por guiones'; 
end if;

if vruta not in (1, 2, 3) then
   RAISE EXCEPTION 'El servidor debe corresponder a los codigis 1, 2 o 3';
end if;


CREATE TABLE abaco_utiles.renglones (  renglon character varying(2000) ) WITH ( OIDS=TRUE );


if vruta = 1 then
   copy abaco_utiles.renglones from 'c:/abaco/gestion/importar/articulos.csv';
  else
    if vruta = 2 then
       vservidor:= '/var/www/html/implementacion_datos/clientes/'; -- Hosting
     else
       vservidor:= '/datacenter/var/www/html/implementacion_datos/clientes/'; -- Datacenter (fibercorp)
    end if;
    vcadena:= 'copy abaco_utiles.renglones from ''' || vservidor || vcuit || '/' || 'articulos.csv' || '''';
    EXECUTE vcadena; 
end if;




CREATE TABLE abaco_utiles.arti
(
  codart	character varying(100),
  nombart       character varying(100),
  idart         integer,
  precio        character(16)   
)
WITH (OIDS=TRUE);




CREATE TABLE abaco_utiles.repetidos
(
 
  codigo	character varying(50),

  ocurrencias   integer
)
WITH (OIDS=TRUE);


select aceptaitem from artr where cod = vrubro into vaceptaiem;

if vaceptaiem = 'N'  then 
   RAISE EXCEPTION 'El rubro ingrsado no acepta items'; 
end if;

insert into abaco_utiles.arti (codart, nombart, precio)
select trim(split_part(renglon, ';', 1)), 
       substring(trim(split_part(renglon, ';', 2)), 1, 100),
       substring(trim(split_part(renglon, ';', 3)), 1, 16)
from abaco_utiles.renglones where trim(split_part(renglon, ';', 1)) <> '' ;

-- Se borran los articulos repetidos para que luego no de error el insert en la tabla art.
insert into abaco_utiles.repetidos (codigo, ocurrencias)
select codart, count(*) from abaco_utiles.arti
group by codart
having count(*) > 1;

delete from abaco_utiles.arti where codart in (select codigo from abaco_utiles.repetidos);
---------------


---Se recupera el prefijo para hacer insert de articulos---


select str_al_punto(vrubro, 1) into vraiz;
select preitem from artr where cod = vraiz into vprefijo;



---INSERT DE ARTICULOS---

insert into art(id, cod, nombre, tipoarta, codartr, 
                              calccant, registrastock, modifnombre, puederegalar, stkcomp, 
                              accesosucursales, cantlinea, accesousuarios) 
select getnextid('art') as id, vprefijo || codart as cod,
       paso_a_minusculas(nombart) as nombre,
       'A' as tipoarta, vrubro, 
       'N' as calccant, 'S' as registrastock, 'N' as modifnombre, 'N' as puederegalar, 'N' as stkcomp, 
       '*' as accesosucursales, 'U' as cantlinea, '*' as accesousuarios
from abaco_utiles.arti
where codart is not null;

RETURN '';
END;
$BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION abaco_utiles.migrar_articulos_de_un_rubro(character varying, character varying, integer)
  OWNER TO abacouser;


----------------------------------------------------------------------------------------------


-------------------------------------------------------------------------
--- Funcion para cargar codigos de barra, a partir de un archivo csv ---- 
-------------------------------------------------------------------------

-- Function: abaco_utiles.migrar_barras(character varying, character varying, integer)

-- DROP FUNCTION abaco_utiles.migrar_barras(character varying, character varying, integer);

CREATE OR REPLACE FUNCTION abaco_utiles.migrar_barras(character varying, character varying, integer)
  RETURNS character varying AS
$BODY$
DECLARE

vrubro    ALIAS FOR $1;
vcuit     ALIAS FOR $2;
vruta     ALIAS FOR $3; 

vcont     integer;
vprefijo  character varying(20); 
vraiz     character varying(50); 

vcadena   character varying;
vservidor character varying;


BEGIN

--- Esta funcion incorpora codigos de barra a articulos que están en cualquier rubro descendiente del rubro raiz 
--- que se indica en el parametro. 
--- La carga se hace a partir de un archivo csv.

-- El primer parametro indica el rubro raiz 
-- El segundo parametro es el cuit del cliente que es obligatorio para el caso que la base no sea local 
-- El tercer parametro se utiliza para indicar la ruta desde donde se leera el archivo csv con los articulos 
--  1  para bases locales 
--  2  para bases en Hosting
--  3  para bases en Datacenter (fibercorp) 


-- El archivo debe venir sin titulos y con los campos delimitados por punto y coma.
-- La campos corresponden a  codigo de articulo del proveedor; codigo de barras. 
-- El nombre sel archivo es 'barras.csv' y para las bases locales dede estar en la carpeta 'c:/abaco/gestion/importar'


-- Los articulos deben estar cargados en el sistema con el prefijo correspondiente al rubro raiz que se indica en el parametro, 
-- seguido del codigo de articulo del proveedor

-- DEPENDIENDO DEL SERVIDOR HABRÁ QUE CAMBIAR LA INSTRUCCION COPY DE ESTA FUNCION


CREATE TABLE abaco_utiles.renglones (  renglon character varying(2000) ) WITH ( OIDS=TRUE );

select count(*) from artr where tipoarta = 'A' and cod = vrubro into vcont;
if vcont = 0 then 
   RAISE EXCEPTION 'No existe el rubro ingresado'; 
end if;

if trim(vcuit) = '' and vruta <> 1 then
   RAISE EXCEPTION 'Debe ingresar el cuit del cliente, separado por guiones'; 
end if;

if vruta not in (1, 2, 3) then
   RAISE EXCEPTION 'El servidor debe corresponder a los codigis 1, 2 o 3';
end if;

if vruta = 1 then
   copy abaco_utiles.renglones from 'c:/abaco/gestion/importar/barras.csv';
  else
    if vruta = 2 then
       vservidor:= '/var/www/html/implementacion_datos/clientes/'; -- Hosting
     else
       vservidor:= '/datacenter/var/www/html/implementacion_datos/clientes/'; -- Datacenter (fibercorp)
    end if;
    vcadena:= 'copy abaco_utiles.renglones from ''' || vservidor || vcuit || '/' || 'barras.csv' || '''';
    EXECUTE vcadena; 
end if;



CREATE TABLE abaco_utiles.barras
(
  codart	character varying(30),
  idart         integer,
  codbar        character varying(100)
)
WITH (OIDS=TRUE);


CREATE TABLE abaco_utiles.barras_repetidas
(
 
  codigo	character varying(100),
  ocurrencias   integer
)
WITH (OIDS=TRUE);


insert into abaco_utiles.barras (codart, codbar)
select substring(trim(split_part(renglon, ';', 1)), 1, 30), substring(trim(split_part(renglon, ';', 2)), 1, 100)
from abaco_utiles.renglones where trim(split_part(renglon, ';', 1)) <> '' ;


---Se recupera el prefijo del rubro raiz para hacer insert de articulos---

select str_al_punto(vrubro, 1) into vraiz;

select preitem from artr where cod = vraiz into vprefijo;

update abaco_utiles.barras barras set idart = art.id
from art
where vprefijo || barras.codart =  art.cod; 


-- Se borran los codigos de baras repetidos para que luego no de error el insert en la tabla art.

insert into abaco_utiles.barras_repetidas(codigo, ocurrencias)
select codbar, count(*) from abaco_utiles.barras
group by codbar
having count(*) > 1;

delete from abaco_utiles.barras where codbar in (select codigo from abaco_utiles.barras_repetidas);

insert into artcodbar (idart, cod)
select idart, codbar 
from abaco_utiles.barras where idart is not null;

RETURN '';
END;
$BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION abaco_utiles.migrar_barras(character varying, character varying, integer)
  OWNER TO abacouser;


------------------------------------------------------------------------------------------------

-- Funcion para actualizar precios por rubro. La variable de precio a actualizar se envia como --
-- parametro de la funcion ---

-- Function: abaco_utiles.act_precios_xrubro(character varying, character varying, character varying, character varying, integer)

-- DROP FUNCTION abaco_utiles.act_precios_xrubro(character varying, character varying, character varying, character varying, integer);

CREATE OR REPLACE FUNCTION abaco_utiles.act_precios_xrubro(character varying, character varying, character varying, character varying, integer)
  RETURNS boolean AS
$BODY$
DECLARE   
varbol                  ALIAS FOR $1;
vrubro   		ALIAS FOR $2;
vprecio   		ALIAS FOR $3;
vcuit   		ALIAS FOR $4;
vruta                   ALIAS FOR $5; 

vcont                   integer;
vaceptaitem             varchar(1);
vprefijo                varchar(4); 
vraiz                   varchar(20);

vcadena 	character varying;
vservidor character varying;


BEGIN
-- Esta funcion permite actualizar precios a todos los articulos de un rubro y para una variable de precios 

-- Los dos primeros parametros corresponden a arbol y rubro.
-- El tercer parametro al codigo de la variable de precio que se va a actualizar. 
-- El cuarto parametro es el cuit del cliente que es obligatorio para el caso que la base no sea local 
-- El quinto parametro se utiliza para indicar la ruta desde donde se leera el archivo csv con los precios:
--  1  para bases locales 
--  2  para bases en Hosting
--  3  para bases en Datacenter (fibercorp) 

-- El archivo debe venir en formato csv, delimitado por ';' y sin titulos. 
-- Los campos de la lista corresponden al codigo de articulo, y al precio de la variable ingresada como parametro
-- El archivo correspondiente a la lista se debe llamar 'precios.csv' y para las bases locales dede estar en la 
-- carpeta 'c:/abaco/gestion/listas' 


-- Los articulos estan cargados en abaco con el codigo que usa el proveedor, precedido por un prefijo de cuatro posiciones en total. 
-- Ese prefijo es el que tiene el rubro raiz correspondiente al rubro ingresado como parametro.
-- La variable de precios que se actualiza viene indicada en el tercer parámetro.

--- SOLO MODIFICA PRECIOS. NO AGREGA ARTICULOS ---


SET CLIENT_ENCODING TO LATIN1;

select count(*) from artr where tipoarta = varbol and cod = vrubro into vcont;
if vcont = 0 then 
   RAISE EXCEPTION 'No existe el rubro ingresado'; 
end if;

if trim(vcuit) = '' and vruta <> 1 then
   RAISE EXCEPTION 'Debe ingresar el cuit del cliente, separado por guiones'; 
end if;

if vruta not in (1, 2, 3) then
   RAISE EXCEPTION 'El servidor debe corresponder a los codigis 1, 2 o 3';
end if;

--Busca el rubro raiz correspondiente al rubro que se ingreso porque es el que tiene cargado el prefijo valido para
--todos los subrubros que decienden de el,

select str_al_punto(vrubro, 1) into vraiz;

select preitem from artr where tipoarta = varbol and cod = vraiz  into vprefijo;

CREATE TABLE abaco_utiles.renglones (  renglon character varying(1000) ) WITH ( OIDS=TRUE );

-- La lista viene en formato csv, delimitado por ';' y sin titulos. Los campos corresponden a codart y precio.

if vruta = 1 then
   copy abaco_utiles.renglones from 'c:/abaco/gestion/listas/precios.csv';
  else
    if vruta = 2 then
       vservidor:= '/var/www/html/implementacion_datos/clientes/'; -- Hosting
     else
       vservidor:= '/datacenter/var/www/html/implementacion_datos/clientes/'; -- Datacenter (fibercorp)
    end if;
    vcadena:= 'copy abaco_utiles.renglones from ''' || vservidor || vcuit || '/' || 'precios.csv' || '''';
    EXECUTE vcadena; 
end if;

-- Elimino las lineas que no tienen codigo --

DELETE FROM abaco_utiles.renglones renglones where trim(split_part(renglon, ';', 1)) = ''; 

CREATE TABLE abaco_utiles.lista

(
  idart integer, 
  codigo character varying(30),
  precio numeric(16,2), 
  es_nuevo character
)
WITH (OIDS=TRUE);
ALTER TABLE abaco_utiles.lista OWNER TO abacouser;


CREATE TABLE abaco_utiles.repetidos
(
  codigo	character varying(50),
  ocurrencias   integer
)
WITH (OIDS=TRUE);

INSERT INTO abaco_utiles.lista(codigo, precio, es_nuevo)
SELECT trim(split_part(renglon, ';', 1)) as codigo, 
       str_a_nro(trim(split_part(renglon, ';', 2))) as precio, 
       'S' as es_nuevo
FROM abaco_utiles.renglones
ORDER BY oid;


-- Se borran los articulos repetidos para que lueego no de error el insert en la tabla prexart

insert into abaco_utiles.repetidos (codigo, ocurrencias)
select codigo, count(*) from abaco_utiles.lista
group by codigo
having count(*) > 1;

delete from abaco_utiles.lista where codigo in (select codigo from abaco_utiles.repetidos);


-- Eliminamos los blancos de las puntas....
update abaco_utiles.lista set codigo = trim(codigo) where codigo <> trim(codigo);

-- Reemplazamos el blanco doble por uno, varias veces, hasta que no modifique ninguno...
update abaco_utiles.lista set codigo = replace(codigo, '    ', ' ') where codigo <> replace(codigo, '    ', ' ');
update abaco_utiles.lista set codigo = replace(codigo, '  ', ' ') where codigo <> replace(codigo, '  ', ' ');
update abaco_utiles.lista set codigo = replace(codigo, '  ', ' ') where codigo <> replace(codigo, '  ', ' ');
update abaco_utiles.lista set codigo = replace(codigo, '  ', ' ') where codigo <> replace(codigo, '  ', ' ');
update abaco_utiles.lista set codigo = replace(codigo, '  ', ' ') where codigo <> replace(codigo, '  ', ' ');

-- Obtengo el idart para los que estan en abaco.   

UPDATE abaco_utiles.lista SET idart = art.id, es_nuevo = 'N'
FROM art
WHERE art.cod = (vprefijo || lista.codigo) and art.tipoarta = varbol and art.codartr like (vrubro ||'%') ;     


-- Se modifican los prexart que ya existian 

UPDATE prexart pxa set valor = abaco_utiles.lista.precio
FROM abaco_utiles.lista
WHERE (cast(abaco_utiles.lista.precio as numeric(16,2)) <> cast(pxa.valor as numeric(16,2)))
      and pxa.idart = abaco_utiles.lista.idart and pxa.idpre = (select id from pre where cod = vprecio)
	  and abaco_utiles.lista.es_nuevo = 'N';

-- Se agregan los nuevo prexart

INSERT INTO prexart(idpre, idart, valor)
SELECT (select id from pre where cod = vprecio), abaco_utiles.lista.idart, abaco_utiles.lista.precio
FROM abaco_utiles.lista 
WHERE abaco_utiles.lista.precio > 0 and abaco_utiles.lista.es_nuevo = 'N'  
      and NOT EXISTS (select * from prexart pxa where pxa.idart = abaco_utiles.lista.idart and pxa.idpre = (select id from pre where cod = vprecio))
ORDER BY abaco_utiles.lista.idart;

RETURN true;

END;
$BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION abaco_utiles.act_precios_xrubro(character varying, character varying, character varying, character varying, integer)
  OWNER TO abacouser;


------------------------------------------------------------------------------------------------------------

-- Function para generar a partir de un archivo csv, con la lista de precios tal cual la manda el proveedor 
-- otro archivo precios.csv solo con las columnas de articulo y precio para usarlo en la función que 
-- incorpora listas de precios por rubro


-- Function: abaco_utiles.actualizar_precios_desde_modelos_lista(character varying, character varying, character varying, character varying, integer)

-- DROP FUNCTION abaco_utiles.actualizar_precios_desde_modelos_lista(character varying, character varying, character varying, character varying, integer);

CREATE OR REPLACE FUNCTION abaco_utiles.actualizar_precios_desde_modelos_lista(character varying, character varying, character varying, character varying, integer)
  RETURNS boolean AS
$BODY$
DECLARE   

varbol                  ALIAS FOR $1;
vrubro   		ALIAS FOR $2;
vprecio   		ALIAS FOR $3;
vcuit   		ALIAS FOR $4;
vruta                   ALIAS FOR $5; 

vcont                   integer;
vmin                    integer;
vmax                    integer;
vtitu_lista             character varying(1000);
vcolpre                 integer;

vlineasaborrar          integer;
vtitulo                 character varying(1000);
vlineastitulo           integer;
vcol_codarti            integer;
vcol_rep                integer;
vcol_repd               integer;
vcol_iva                integer;
vcol_vta                integer;
vcol_vtad               integer;
vcol_desp1              integer;
vcol_desp2              integer;
vcol_desp3              integer;

vprefijo                varchar(4); 
vraiz                   varchar(20);
vcadena 	        character varying;
vservidor               character varying;

BEGIN

-- Esta funcion permite actualizar precios a partir de un archivo lista.csv, que surge del archivo excel 
-- tal cual lo mando el proveedor. 
-- Esto significa sin ninguna manipulación previa, solamente generar todo en una sola hoja en el caso que haya varias
-- solapas.

-- Esta función utilizará una tabla modelos_listas del esquema abaco_utiles, donde se indica para un rubro dado en que columna
-- de la lista viene el articulo, en que columna el precio de reposicion, en que columna el de reposiscion en dolares, y el de 
-- otras variables de precios. 

--- PARAMETROS DE LA FUNCION ---
-- Los dos primeros parametros corresponden a arbol y rubro.
-- El tercer parametro al codigo de la variable de precio que se va a actualizar. 
-- El cuarto parametro es el cuit del cliente que es obligatorio para el caso que la base no sea local 
-- El quinto parametro se utiliza para indicar la ruta desde donde se leera el archivo csv con los precios:
--  1  para bases locales 
--  2  para bases en Hosting
--  3  para bases en Datacenter (fibercorp) 

-- El archivo se llama 'lista.csv', viene delimitado por ';' y para las bses locales tiene que estar en 'c:/abaco/gestion/listas'. 

-- De esta manera segun los parametros de la funcion, rubro y variable de precios, el sistema tomara para el modelo
-- de lista de ese rubro las columnas correspondientes a codigo de articulo y a esa variable de precio y actualizara
-- los precios para esa variable y ese rubro

-- Esto permite que si un proveedor manda en una misma lista dos o más variables de precios, la lista original no se manipule y
-- se pueden con distintos procesos especiales llamar a la función con variables de precios diferentes.

-- Las variables de precios contempladas en esta función son:
-- reposicion, reposicion en dolares, venta, venta en dolares, iva, descuento1 proveedor, descuento2 proveedor y 
-- descuento3 proveedor.

-- Esta función tambien descartará la cntidad de lineas al inicio que se indiquen en la tabla para ese modelo y
-- controlará que si varian los titulos de la lista con respecto a los que se defieron para ese modelo se emita un aviso y
-- el proceso no se genere. 


SET CLIENT_ENCODING TO LATIN1;

CREATE TABLE abaco_utiles.renglones (  renglon character varying(2000) ) WITH ( OIDS=TRUE );

select count(*) from abaco_utiles.modelos_listas where rubro = vrubro into vcont;

if vcont = 0 then
   RAISE EXCEPTION 'No existe modelo definido para la lista del rubro ingresado'; 
end if;


if trim(vcuit) = '' and vruta <> 1 then
   RAISE EXCEPTION 'Debe ingresar el cuit del cliente, separado por guiones'; 
end if;

if vruta not in (1, 2, 3) then
   RAISE EXCEPTION 'El servidor debe corresponder a los codigis 1, 2 o 3';
end if;

select count(*) from artr where tipoarta = varbol and cod = vrubro into vcont;
if vcont = 0 then 
   RAISE EXCEPTION 'No existe el rubro ingresado'; 
end if;

select str_al_punto(vrubro, 1) into vraiz;

select preitem from artr where tipoarta = varbol and cod = vraiz  into vprefijo;


select lineasaborrar, titulo, lineastitulo, col_codarti, col_rep, col_repd,
       col_iva, col_vta, col_vtad, col_desp1, col_desp2, col_desp3 
from abaco_utiles.modelos_listas
where rubro = vrubro
into   vlineasaborrar, vtitulo, vlineastitulo, vcol_codarti, vcol_rep, 
       vcol_repd, vcol_iva, vcol_vta, vcol_vtad, vcol_desp1, vcol_desp2, vcol_desp3;

-- Segun el parametro ingresado se determina desde donde se hace el copy del archivo

if vruta = 1 then
   copy abaco_utiles.renglones from 'c:/abaco/gestion/listas/lista.csv';
  else
    if vruta = 2 then
       vservidor:= '/var/www/html/implementacion_datos/clientes/'; -- Hosting
     else
       vservidor:= '/datacenter/var/www/html/implementacion_datos/clientes/'; -- Datacenter (fibercorp)
    end if;
    vcadena:= 'copy abaco_utiles.renglones from ''' || vservidor || vcuit || '/' || 'lista.csv' || '''';
    EXECUTE vcadena; 
end if;



select min(oid) from abaco_utiles.renglones into vmin;

vmax:= vmin + vlineasaborrar - 1;

-- Se borran las lineas indicadas en el modelo como lineas a descartar
delete from abaco_utiles.renglones where oid between vmin and vmax;

select min(oid) from abaco_utiles.renglones into vmin;

select renglon from abaco_utiles.renglones where oid = vmin  into vtitu_lista;


-- Se compara el titulo que trajo ahora la lista con el que hay definido en la tabla para ese modelo
-- Si hay error avisa y no sigue.

if vtitulo <> vtitu_lista then
   RAISE EXCEPTION 'No coincide el titulo de la lista enviada con el titulo original.'; 
end if;


vmax:= vmin + vlineastitulo - 1;

-- Se borran las lineas de titulos
delete from abaco_utiles.renglones where oid between vmin and vmax;
    
-- Segun la variable de precios que se ingresa como paametro, se fija en vcolpre el numero de columna que utilizara 
-- el split_part para recuperar el precio.
 
if vprecio = 'REP' 
   then vcolpre:= vcol_rep;
end if;   

if vprecio = 'REPD' 
   then vcolpre := vcol_repd;
end if;   

if vprecio = 'IVA' 
   then vcolpre := vcol_iva;
end if;   

if vprecio = 'VTA' 
   then vcolpre:= vcol_vta;
end if;   

if vprecio = 'VTAD' 
   then vcolpre := vcol_vtad;
end if;   


if vprecio = 'DESP1' 
   then vcolpre := vcol_desp1;
end if;   

if vprecio = 'DESP2' 
   then vcolpre:= vcol_desp2;
end if;   

if vprecio = 'DESP3' 
   then vcolpre := vcol_dsp3;
end if;   


CREATE TABLE abaco_utiles.lista

(
  idart integer, 
  codigo character varying(30),
  precio numeric(16,2), 
  es_nuevo character
)
WITH (OIDS=TRUE);
ALTER TABLE abaco_utiles.lista OWNER TO abacouser;


CREATE TABLE abaco_utiles.repetidos
(
  codigo	character varying(50),
  ocurrencias   integer
)
WITH (OIDS=TRUE);


-- Se insertan en la tabla lista los valores de codigo de articulo y precio 

INSERT INTO abaco_utiles.lista(codigo, precio, es_nuevo)
SELECT split_part(renglon, ';', vcol_codarti) as codigo, 
       str_a_nro(split_part(renglon, ';', vcolpre)) as precio, 
       'S' as es_nuevo
FROM abaco_utiles.renglones
where trim(split_part(renglon, ';', vcol_codarti)) <> '' and str_solo_digitos(split_part(renglon, ';', vcolpre)) <> '' 
ORDER BY oid;


-- Se borran los articulos repetidos para que lueego no de error el insert en la tabla prexart

insert into abaco_utiles.repetidos (codigo, ocurrencias)
select codigo, count(*) from abaco_utiles.lista
group by codigo
having count(*) > 1;

delete from abaco_utiles.lista where codigo in (select codigo from abaco_utiles.repetidos);

-- Eliminamos los blancos del codigo en las puntas....
update abaco_utiles.lista set codigo = trim(codigo) where codigo <> trim(codigo);

-- Reemplazamos el blanco doble por uno, varias veces, hasta que no modifique ninguno...
update abaco_utiles.lista set codigo = replace(codigo, '    ', ' ') where codigo <> replace(codigo, '    ', ' ');
update abaco_utiles.lista set codigo = replace(codigo, '  ', ' ') where codigo <> replace(codigo, '  ', ' ');
update abaco_utiles.lista set codigo = replace(codigo, '  ', ' ') where codigo <> replace(codigo, '  ', ' ');
update abaco_utiles.lista set codigo = replace(codigo, '  ', ' ') where codigo <> replace(codigo, '  ', ' ');
update abaco_utiles.lista set codigo = replace(codigo, '  ', ' ') where codigo <> replace(codigo, '  ', ' ');

-- Obtengo el idart para los que estan en abaco.   

UPDATE abaco_utiles.lista SET idart = art.id, es_nuevo = 'N'
FROM art
WHERE art.cod = (vprefijo || lista.codigo) and art.tipoarta = varbol and art.codartr like (vrubro ||'%') ;     


-- Se modifican los prexart que ya existian 

UPDATE prexart pxa set valor = cast(abaco_utiles.lista.precio as numeric(16,2))
FROM abaco_utiles.lista
WHERE (cast(abaco_utiles.lista.precio as numeric(16,2)) <> cast(pxa.valor as numeric(16,2)))
      and pxa.idart = abaco_utiles.lista.idart and pxa.idpre = (select id from pre where cod = vprecio)
	  and abaco_utiles.lista.es_nuevo = 'N';

-- Se agregan los nuevo prexart

INSERT INTO prexart(idpre, idart, valor)
SELECT (select id from pre where cod = vprecio), abaco_utiles.lista.idart, cast(abaco_utiles.lista.precio as numeric(16,2))
FROM abaco_utiles.lista 
WHERE abaco_utiles.lista.precio > 0 and abaco_utiles.lista.es_nuevo = 'N'  
      and NOT EXISTS (select * from prexart pxa where pxa.idart = abaco_utiles.lista.idart and pxa.idpre = (select id from pre where cod = vprecio))
ORDER BY abaco_utiles.lista.idart;


RETURN true;

END;
$BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION abaco_utiles.actualizar_precios_desde_modelos_lista(character varying, character varying, character varying, character varying, integer)
  OWNER TO abacouser;


-------------------------------------------------------------------------------------------------------------

select aaVersion('488.07','488.06');

